const {
  src,
  dest,
  parallel,
  series,
  watch
} = require('gulp')

const del = require('del')
const browserSync = require('browser-sync')

const loadPlugins = require('gulp-load-plugins')

const plugins = loadPlugins()
const bs = browserSync.create()
const cwd = process.cwd()

let config = {
  build: {
    buildSrc: 'src',
    dist: 'dist',
    temp: 'temp',
    public: 'public',
    paths: {
      styles: 'assets/styles/*.scss',
      scripts: 'assets/scripts/*.js',
      pages: '*.html',
      images: 'assets/images/**',
      fonts: 'assets/fonts/**'
    }
  }
}

try{
  let loadConfig = require(`${cwd}/pages.config.js`)
  config = Object.assign({}, config, loadConfig)
} catch(e) {

}


const { buildSrc, dist, temp, public, paths } = config.build
const { styles, scripts, pages, images, fonts} = paths

const clean = () => {
  return del([dist, temp])
}

const style = () => {
  return src(styles, {
      base: buildSrc,
      cwd: buildSrc
    })
    .pipe(plugins.sass({
      outputStyle: 'expanded'
    }))
    .pipe(dest(temp))
    .pipe(bs.reload({
      stream: true
    }))
}

const script = () => {
  return src(scripts, {
      base: buildSrc,
      cwd: buildSrc
    })
    .pipe(plugins.babel({
      presets: [require('@babel/preset-env')]
    }))
    .pipe(dest(temp))
    .pipe(bs.reload({
      stream: true
    }))
}

const page = () => {
  return src(pages, {
      base: buildSrc,
      cwd: buildSrc
    })
    .pipe(plugins.swig({
      data: config.data,
      defaults: {
        cache: false
      }
    })) // 防止模板缓存导致页面不能及时更新
    .pipe(dest(temp))
    .pipe(bs.reload({
      stream: true
    }))
}

const image = () => {
  return src(images, {
      base: buildSrc,
      cwd: buildSrc
    })
    .pipe(plugins.imagemin())
    .pipe(dest(dist))
}

const font = () => {
  return src(fonts, {
      base: buildSrc,
      cwd: buildSrc
    })
    .pipe(plugins.imagemin())
    .pipe(dest(dist))
}

const extra = () => {
  return src('**', {
      base: public,
      cwd: public
    })
    .pipe(dest(dist))
}

const serve = () => {
  watch(styles, {cwd: buildSrc}, style)
  watch(scripts, {cwd: buildSrc}, script)
  watch(pages, {cwd: buildSrc}, page)
  // watch('src/assets/images/**', image)
  // watch('src/assets/fonts/**', font)
  // watch('public/**', extra)
  watch([
    images,
    fonts
  ], { cwd: buildSrc}, bs.reload)

  watch('**', {cwd: public}, bs.reload)

  bs.init({
    notify: false,
    port: 2080,
    // open: false,
    // files: 'dist/**',
    server: {
      baseDir: [temp, buildSrc, public],
      routes: {
        '/node_modules': 'node_modules'
      }
    }
  })
}

const useref = () => {
  return src(pages, {
      base: temp,
      cwd: temp
    })
    .pipe(plugins.useref({
      searchPath: [temp, '.']
    }))
    // html js css
    .pipe(plugins.if(/\.js$/, plugins.uglify()))
    .pipe(plugins.if(/\.css$/, plugins.cleanCss()))
    .pipe(plugins.if(/\.html$/, plugins.htmlmin({
      collapseWhitespace: true,
      minifyCSS: true,
      minifyJS: true
    })))
    .pipe(dest(dist))
}

const compile = parallel(style, script, page)

// 上线之前执行的任务
const build = series(
  clean,
  parallel(
    series(compile, useref),
    image,
    font,
    extra
  )
)

const develop = series(compile, serve)

module.exports = {
  clean,
  build,
  develop
}
